/*
 * Hibernate Validator, declare and validate application constraints
 *
 * License: Apache License, Version 2.0
 * See the license.txt file in the root directory or <http://www.apache.org/licenses/LICENSE-2.0>.
 */
package com.usefullc.system.validator;

import com.usefullc.common.enums.ValidTypeEnum;
import com.usefullc.common.exception.BizException;
import io.swagger.annotations.ApiModelProperty;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.reflect.FieldUtils;
//import org.apache.commons.validator.EmailValidator;
//import org.apache.commons.validator.UrlValidator;
//import org.apache.commons.validator.routines.CurrencyValidator;

import java.lang.reflect.Field;
import java.math.BigDecimal;
import java.util.Date;
import java.util.regex.Pattern;

/**
 *
 *
 */
public class UsefulValidator  {


	public static void validator(Object requestParam,UsefulValid usefulValid) {
		try{
			Field[] declaredFields = FieldUtils.getAllFields(requestParam.getClass());
			for (Field declaredField : declaredFields) {
				if(usefulValid.update() && declaredField.getName().equals("id")){
				    declaredField.setAccessible(true);
					Object idValue = declaredField.get(requestParam);
					declaredField.setAccessible(false);
					if(idValue == null){
						throw new BizException("ID不能为空",false);
					}
				}
				if (!declaredField.isAnnotationPresent(UsefulPropertyVerify.class)) {
					continue;
				}
				UsefulPropertyVerify usefulPropertyVerify = declaredField.getAnnotation(UsefulPropertyVerify.class);
				//动作匹配
				boolean matchAction = true;
				switch (usefulPropertyVerify.action()){
					case SAVE:if(!usefulValid.save()){ matchAction = false; };break;
					case UPDATE:if(!usefulValid.update()){ matchAction = false; };break;
					case QUERY:if(!usefulValid.query()){ matchAction = false; };break;
					case DEL:if(!usefulValid.del()){ matchAction = false; };break;
				}
				if(!matchAction){
					continue;
				}
				//end
				declaredField.setAccessible(true);
				Object fieldValue = declaredField.get(requestParam);
				declaredField.setAccessible(false);
				String filedName = declaredField.getName();
				String filedCnName = filedName;
				ApiModelProperty apiModelProperty = declaredField.getAnnotation(ApiModelProperty.class);
				if(apiModelProperty != null && StringUtils.isNotEmpty(apiModelProperty.notes())){
					filedCnName = apiModelProperty.notes();
				}

				//非空
				if(usefulPropertyVerify.required() && (fieldValue == null || StringUtils.isBlank(fieldValue.toString()))){
					throw new BizException(filedCnName+"不能为空",false);
				}
				if(fieldValue == null || StringUtils.isBlank(fieldValue.toString())){
					continue;
				}

				//字符长度
				if (fieldValue instanceof String) {
					int minLen = usefulPropertyVerify.minLen();
					int maxLen = usefulPropertyVerify.maxLen();
					if(fieldValue.toString().length() > maxLen || fieldValue.toString().length() < minLen){
						throw new BizException(filedCnName+"长度必须在"+minLen+"和"+maxLen+"之间",false);
					}

					//数字大小
				}else if(fieldValue instanceof Integer || fieldValue instanceof Long){
					long min = usefulPropertyVerify.min();
					long max = usefulPropertyVerify.max();
					Long value = Long.valueOf(fieldValue.toString());
					if(value > max || value < min){
						throw new BizException(filedCnName+"大小必须在"+min+"和"+max+"之间",false);
					}
					//时间
				}else if(fieldValue instanceof Date){
					//判断时间格式化是否正确 todo

					//小数
				}else  if(fieldValue instanceof BigDecimal){
					//判断 todo
				}

				//特殊字段校验
				ValidTypeEnum type = usefulPropertyVerify.type();
				switch (type){
					case EMPTY:break;
					case URL:validatorUrl(filedCnName,fieldValue.toString(),usefulPropertyVerify);break;
					case MONEY:validatorMoney(filedCnName,fieldValue.toString(),usefulPropertyVerify);break;
					case DATE:validatorDate(filedCnName,fieldValue.toString(),usefulPropertyVerify);break;
					case DIGIT:validatorRoundNumber(filedCnName,fieldValue.toString(),usefulPropertyVerify);break;
					case EMAIL:validatorEmail(filedCnName,fieldValue.toString(),usefulPropertyVerify);break;
					case ZIP_CODE:validatorZipCode(filedCnName,fieldValue.toString(),usefulPropertyVerify);break;
					case PHONE:validatorPhone(filedCnName,fieldValue.toString(),usefulPropertyVerify);break;
					case MOBILE:validatorMobile(filedCnName,fieldValue.toString(),usefulPropertyVerify);break;
					case ID_CARD:validatorIdCard(filedCnName,fieldValue.toString(),usefulPropertyVerify);break;
					case BANK_CARD:validatorBankCard(filedCnName,fieldValue.toString(),usefulPropertyVerify);break;
				}
			}


		}catch (Exception e){
			throw new BizException(e.getMessage(),e);
		}
	}

	private static void validatorUrl(String cnName,String value,UsefulPropertyVerify usefulPropertyVerify){
//		UrlValidator urlValidator = new UrlValidator();
//		if (urlValidator.isValid(value)) {
//			throw new BizException(cnName+"格式不正确",false);
//		}
	}

	private static void validatorMoney(String cnName,String value,UsefulPropertyVerify usefulPropertyVerify){
//		if (CurrencyValidator.getInstance().isValid(value)) {
//			throw new BizException(cnName+"格式不正确",false);
//		}

	}

	private static void validatorDate(String cnName,String value,UsefulPropertyVerify usefulPropertyVerify){

	}
	private static void validatorRoundNumber(String cnName,String value,UsefulPropertyVerify usefulPropertyVerify){

	}
	private static void validatorEmail(String cnName,String value,UsefulPropertyVerify usefulPropertyVerify){
//		if (!EmailValidator.getInstance().isValid(value)) {
//			throw new BizException(cnName+"格式不正确",false);
//		}
	}
	private static void validatorZipCode(String cnName,String value,UsefulPropertyVerify usefulPropertyVerify){
	    if(!Pattern.matches("^[1-9]\\d{5}$", value)){
			throw new BizException(cnName+"格式不正确",false);
		}
	}
	private static void validatorPhone(String cnName,String value,UsefulPropertyVerify usefulPropertyVerify){
		if(!Pattern.matches("^((0\\d{2,3}-\\d{7,8})|(1[3456789]\\d{9}))$", value)){
			throw new BizException(cnName+"格式不正确",false);
		}
	}
	private static void validatorMobile(String cnName,String value,UsefulPropertyVerify usefulPropertyVerify){
		if(!Pattern.matches("^(0|86|17951)?(13[0-9]|15[012356789]|16[6]|19[89]]|17[01345678]|18[0-9]|14[579])[0-9]{8}$", value)){
			throw new BizException(cnName+"格式不正确",false);
		}
	}
	private static void validatorIdCard(String cnName,String value,UsefulPropertyVerify usefulPropertyVerify){

	}

	private static void validatorBankCard(String cnName,String value,UsefulPropertyVerify usefulPropertyVerify){

	}

	public static void main(String[] args) {
//		validatorZipCode("邮政编码","1412000");
		validatorMobile("手机号码","15267164683",null);
	}
}
